
var routeExample = angular.module('routeExample', ['ngResource', 'ngRoute'/*, 'ngSwitchWhen', 'ngChange'*/]);
routeExample.directive('exampleTime', function() {
    return {
        //http://amitgharat.wordpress.com/2013/06/08/the-hitchhikers-guide-to-the-directive/
        restrict: 'EA', //E - element, A - attribte C - css class name M - comments. Can an be EA also.
        templateUrl: '/templates/time-directive.html', //template: "<label>1234</label>",
        compile: function(element, attr, transclusionFunc) {// Compile creates link function, therefore our link is not used! Directive element and attr.
            console.log("Compiling directive A");
            return function(scope, iterStartElement, attr) {
                console.log("Linking directive");
            };
        }
        /*,
         link: function(scope, iterStartElement, attr) {
         //
         console.log("Linking directive");
         }*/
    };
});
routeExample.config(function($routeProvider) {
    $routeProvider.
            when('/page1', {templateUrl: 'templates/page1.html', controller: Page1}).
            when('/page2/:pageID', {templateUrl: 'templates/page2.html', controller: Page2}).
            when('/page3/:pageID', {templateUrl: 'templates/page3.html', controller: Page3}).
            when('/page4/:pageID', {templateUrl: 'templates/page4.html', controller: Page4}).
            when('/userstory', {templateUrl: 'templates/userstory.html', controller: UserStory}).
            when('/law/:type/:short/:paragraph/:fragment/:point', {templateUrl: 'templates/law.html', controller: LawPart}).
            when('/piusa', {templateUrl: 'templates/piusa.html', controller: Piusa}).
            when('/book', {templateUrl: 'templates/book.html', controller: Book}).
            when('/model/:companyID', {templateUrl: 'templates/model.html', controller: Model}).
            otherwise({redirectTo: '/timer'});
});
routeExample.factory('Person', function($resource) {
    var PersonClass = $resource('/rest/persons/:personId', null, null);
    return PersonClass;
});
routeExample.factory('UserStoryService', function($resource) {
    var UserStoryService = {
        translation: {
            asSentence: "As a ",
            wantSentence: ", I want ",
            soSentence: " so that "
        },
        storyNumber: 0,
        roleNumber: 0,
        roles: [
            {id: 0, roleName: "Company Owner"},
            {id: 1, roleName: "Company It Techinchan"}
        ],
        stories: [
        ],
        add: function(story) {
            this.stories.push(story);
            return this.stories;
        },
        newInstance: function() {
            var ret = {
                id: this.storyNumber,
                role: null,
                goal: null,
                benefit: null,
                storyPoints: null
            };
            this.storyNumber++;
            return ret;
        }
    };
    return UserStoryService;
});
routeExample.factory('PiusaService', function() {
    var IT = "I.T.",
            TR = "T.R.",
            LR = "L.R.",
            TP = "T.P.",
            KH = "K.H.",
            ES = "E.S.",
            CMS = "C.M.S.",
            KH = "K.H.",
            KV = "K.V.",
            KU = "K.U.",
            REEDE = "Reede", LAUPAEV = "Laupäev", PYHAPAEV = "Pühapäev", ESMASPAEV = "Esmaspäev";
    var FRIDAY_HOURS = 2;
    var SATURDAY_HOURS = 24;
    var SUNDAY_HOURS = 12;//24;
    var MONDAY_HOURS = 0;//12;
    var STOVE_VOLUME = 100;// 100L ruumipuid ühe kütekorra kohta
    var OVEN_VOLUME = 150;// 150L ruumipuid ühe kütekorra kohta
    var SAUNA_VOLUME = 200;// 200L ruumipuid ühe kütekorra kohta
    var distance = 600;
    var additionalDistance = 150;
    var casCost = 1.284; //http://www.nesteoil.ee/
    var volumeCost = 35;
    var casExpense = 8; //100km
    var dayCoustPerPerson = 5.0;
    var shouldDoRounding = true;
    var shouldDoFlooring = false;
    var groups = [
        {name: IT, persons: [{name: IT}, {name: ES}, {name: CMS}, {name: KU}], hours: FRIDAY_HOURS + SATURDAY_HOURS + SUNDAY_HOURS},
        {name: TP, persons: [{name: TP}], hours: 5 + FRIDAY_HOURS + SATURDAY_HOURS + SUNDAY_HOURS},
        {name: TR, persons: [{name: TR}, {name: LR}, {name: "L.1."}, {name: "L.2."}], hours: 3 + SATURDAY_HOURS}
    ];
    var heaters = [
        {
            name: "Pliit", //Pliit ja ahi - tagatuba
            volume: STOVE_VOLUME,
            heatingDays: [
                {dayName: LAUPAEV, counts: [[IT, TP, KU], [IT, TP, KU], [IT, TR, TP, KU]], countGroups: []},
                {dayName: PYHAPAEV, counts: [[IT, TR, TP, KU]/*, [IT, TR, TP, KU], [IT, TR, TP, KU]*/], countGroups: []}/*,
                {dayName: ESMASPAEV, counts: [[IT, TR, TP, KU]], countGroups: []}*/
            ]
        },
        {
            name: "Ahi", // Söögi toa ahi
            volume: OVEN_VOLUME,
            heatingDays: [
                {dayName: LAUPAEV, counts: [[IT, TR, TP, KU], [IT, TR, TP, KU]], countGroups: []}/*,
                {dayName: PYHAPAEV, counts: [[IT, TR, TP, KU]], countGroups: []}*/
            ]
        },
        {
            name: "Saun",
            volume: SAUNA_VOLUME,
            heatingDays: [
                {dayName: LAUPAEV, counts: [[IT, TR, TP, KU]], countGroups: []}
            ]
        }
    ];
    var carGroups = [
        {
            name: TP,
            persons: [
                {name: TP}
            ],
            size: function() {
                return this.persons.length;
            }
        },
        {
            name: IT,
            persons: [
                {name: IT},
                {name: ES},
                {name: CMS},
                {name: KU}
            ],
            size: function() {
                return this.persons.length;
            }
        },
        /*{
            name: "Näidis Car",
            persons: [
                {name: KU},
                {name: IT},
                {name: ES},
                {name: CMS}
            ],
            size: function() {
                return this.persons.length;
            }
        },*/
        {
            name: "Näidis Full Car",
            persons: [
                {name: TP},
                {name: KU},
                {name: IT},
                {name: ES},
                {name: CMS}
            ],
            size: function() {
                return this.persons.length;
            }
        }
    ];
    var PiusaService = {
        // Sõitmine
        shouldDoRounding: shouldDoRounding,
        shouldDoFlooring: shouldDoFlooring,
        distance: distance,
        additionalDistance: additionalDistance,
        casCost: casCost,
        casExpense: casExpense, // l/100km
        carGroups: carGroups,
        totalDistance: function() {
            return this.distance + this.additionalDistance;
        },
        kmCasExpense: function() {
            return this.casExpense / 100;
        },
        totalCasExpense: function() {
            return this.kmCasExpense() * this.totalDistance();
        },
        totalCasCost: function() {
            return this.totalCasExpense() * this.casCost;
        },
        carGroupPersonCost: function(group) {
            return this.rounding(this.totalCasCost() / group.size());
        },
        // Majutus
        dayCoustPerPerson: dayCoustPerPerson,
        findGroup: function(name) {
            var group;
            for (group in this.house.groups) {
                if (this.house.groups[group].name === name) {
                    return this.house.groups[group];
                }
            }
            return null;
        },
        personsNumber: function() {
            var ret = 0;
            this.house.groups.forEach(function(group) {
                ret += group.persons.length;
            });
            return ret;
        },
        groupHouseDayCost: function(group) {
            return group.persons.length * this.dayCoustPerPerson;
        },
        groupDays: function(group) {
            return this.flooring(this.rounding(group.hours / 24));
        },
        groupHouseCost: function(group) {
            return this.rounding(this.groupDays(group) * this.groupHouseDayCost(group));
        },
        // Kütmine
        volumeCost: volumeCost,
        getHeaters: function() {
            console.log("getHeaters");
            this.onDemandInit();
            this.getHeaterCalls++;
            return this.house.heaters;
        },
        getGroupsNumber: function() {
            return this.house.groups.length;
        },
        getHeatingPricePerGroup: function() {
            return  this.rounding(this.getHouse().totalVolumeCost() / this.getGroupsNumber());
        },
        getHouse: function() {
            this.onDemandInit();
            return this.house;
        },
        house: {
            volumeCost: volumeCost,
            groups: groups,
            heaters: heaters,
            totalVolume: function() {
                var ret = 0, day, pos, heater, attrName;
                for (attrName in this.heaters) {
                    heater = this.heaters[attrName];
                    for (pos in heater.heatingDays) {
                        day = heater.heatingDays[pos];
                        ret += day.counts.length * heater.volume;
                    }
                }
                return ret / 1000;
            },
            totalVolumeCost: function() {
                return this.totalVolume() * volumeCost;
            }
        },
        initialized: false,
        onDemandInit: function() {
            if (!this.initialized) {
                this.init();
            }
        },
        init: function() {
            console.log("init");
            this.addFunctions();
            this.transformHeaters();
            this.initialized = true;
        },
        addFunctions: function() {
            console.log("addFunctions");
            for (var gpos in this.house.groups) {//--------- Groups functions
                var group = this.house.groups[gpos];
                group.heatingPriceSum = 0.0;
                group.service = this;
                group.size = function() {
                    return this.persons.length;
                };
                group.addGroupPrice = function(addable) {
                    this.heatingPriceSum += addable;
                };
                group.getGroupHeatingPrice = function() {
                    return this.service.rounding(this.heatingPriceSum);
                };
            }
            for (var hpos in this.house.heaters) {//--------- Heaters functions
                var heater = this.house.heaters[hpos];
                heater.findDay = function(name) {
                    for (var dpos in this.heatingDays) {
                        var day = this.heatingDays[dpos];
                        if (day.dayName === name) {
                            return day;
                        }
                    }
                    return null;
                };
            }
        },
        transformHeaters: function() {
            for (var pos in this.house.heaters) {
                var heater = this.house.heaters[pos];
                this.transformHeater(heater);
            }
        },
        transformHeater: function(heater) {
            for (var pos in heater.heatingDays) {
                var day = heater.heatingDays[pos];
                this.transformHeaterDay(day, heater);
            }
        },
        transformHeaterDay: function(day, heater) {
            day.getHeatingPrice = function() {
                var ret = 0;
                for (var i in day.countGroups) {
                    var heatingProcedure = day.countGroups[i];
                    ret += heatingProcedure.getProcedurePrice();
                }
                return ret;
            };
            this.transformHeaterDayCounts(day.counts, day.countGroups, heater);
        },
        getHeaterCalls: 0,
        transformHeaterDayCounts: function(procedures, countGroups, heater) {
            for (var i in procedures) {
                var procedureGroupNames = procedures[i];
                var heatingProcedure = {
                    service: this,
                    heater: heater,
                    groups: new Array(),
                    getParticipantsNumber: function() {
                        var ret = 0;
                        for (var i in this.groups) {
                            ret += this.groups[i].size();
                        }
                        return ret;
                    },
                    getProcedurePrice: function() {
                        return (this.service.volumeCost * (this.heater.volume / 1000));
                    },
                    getPricePerPerson: function() {
                        return this.service.rounding(this.getProcedurePrice() / this.getParticipantsNumber());
                    },
                    getGroupPrice: function(group) {
                        var ret = this.service.rounding(group.size() * this.getPricePerPerson());
                        var addResult;
                        if (this.service.getHeaterCalls === 0 || this.service.getHeaterCalls === 1) {
                            addResult = "ADDED";
                            group.addGroupPrice(ret);
                            console.log("getGroupPrice: " + group.name + ", price: " + ret + " : " + addResult);
                        }
                        return ret;
                    }
                };
                countGroups.push(heatingProcedure);
                this.transformNames(procedureGroupNames, heatingProcedure);
            }
        },
        transformNames: function(procedureGroupNames, heatingProcedure) {
            var namesPos;
            for (namesPos in procedureGroupNames) {
                var name = procedureGroupNames[namesPos];
                var group = this.findGroup(name);
                if (group !== null) {
                    heatingProcedure.groups.push(group);
                }
            }
        },
        rounding: function(num) {
            if (this.shouldDoRounding) {
                return Math.round(num * 100) / 100;
            }
            return num;
        },
        flooring: function(number) {
            if (this.shouldDoFlooring) {
                return Math.floor(number);
            }
            return number;
        },
        checkNumber: function(a, b) {
            return (angular.isDefined(a)
                    && angular.isDefined(b)
                    && a
                    && b
                    && !isNaN(a)
                    && !isNaN(b));
        },
        equalityCheck: function(a, b) {
            if (this.checkNumber(a, b)) {
                if (a === b) {
                    return "TÕSI";
                } else {
                    return "VALE";
                }
            } else {
                return null;
            }
        }
    };
    return PiusaService;
});
routeExample.factory('ModelService', function(Company) {
    var VIEW = "view", EDIT = "edit", DELETE = "delete", SINGLE = "single", LIST = "list";
    //company.persons [list | single] in "" view (panel) in modes [view/edit/delete].
    var ModelService = {
        LIST: LIST,
        SINGLE: SINGLE,
        VIEW: VIEW,
        EDIT: EDIT,
        DELETE: DELETE,
        config: {
            attributes: [
                {
                    name: "company.persons",
                    classType: "ee.has.Person",
                    type: LIST,
                    panels: [
                        {
                            name: "CompanyPersonsA",
                            template: "template.html"
                        }
                    ],
                    single: {
                    }
                }
            ]
        },
        build: function(scope) {
            scope.companies = Company.query();
        }
    };
    return ModelService;
});
routeExample.factory('Company', function($resource) {
    var CompanyClass = $resource('/rest/companies/:companyId', null, null);
    return CompanyClass;
});
routeExample.factory('BookService', function($resource, $http) {
    var BookService = {
        queryBooks: function(scope) {
            $http({method: 'GET', url: scope.url + scope.suffix}).
                    success(function(data) {
                        var books = [];
                        var booksChapters = [];
                        for (var bookPos in data.books) {
                            var book = data.books[bookPos];
                            books.push(book);
                            if (book.chapters) {
                                for (var i = 1; i <= book.chapters; i++) {
                                    var suffix = "+" + i;
                                    if (book.abbr) {
                                        var bookStr = {url: scope.url + "?q=" + book.abbr + suffix, bookChapter: book.abbr + "+" + i + ".json"};
                                        booksChapters.push(bookStr);
                                    }
                                }
                            }
                        }
                        scope.books = books;
                        scope.booksChapters = booksChapters;
                    }).
                    error(function(data, status) {
                        scope.dataError = data || "Request failed";
                        scope.status = status;
                    });
        }
    };
    return BookService;
});
routeExample.factory('LawService', function() {
    var LawService = {
        url: "https://www.riigiteataja.ee",
        actUrl: "/akt",
        getActUrlById: function(actId) {
            return this.url + this.actUrl + "/" + actId;
        },
        getActUrlByIdLatest: function(actId) {
            return this.getActUrlById(actId) + "?leiaKehtiv";
        },
        getActUrl: function(law, paragraph, fragment, point) {
            if (law !== undefined && law !== null) {
                var ret = this.getActUrlByIdLatest(law.actId);
                if (paragraph !== undefined && paragraph !== null) {
                    ret += "#";
                    ret += "para" + paragraph;
                    if (fragment !== undefined && fragment !== null) {
                        ret += "lg" + fragment;
                        if (point !== undefined && point !== null) {
                            ret += "p" + point;
                        }
                    }
                }
                return ret;
            }
            return null;
        },
        stringToReference: function(str) {
            var ret = {
                short: null, paragraph: null, fragment: null, point: null, url: null, law: null
            };
            var parts = str.split(" ");
            if (parts.length >= 1) {
                ret.short = parts[0];
                ret.law = this.findLawByShort(ret.short);
                if (ret.law !== null) {
                    ret.url = this.getActUrl(ret.law);
                }
                if (parts.length >= 3 && parts[1] === "§") {
                    ret.short = parts[0];
                    //ret.law = this.findLawByShort(ret.short);
                    ret.paragraph = parts[2];
                    if (parts.length >= 5 && (parts[3] === "lg" || parts[3] === "lg.")) {// part
                        ret.fragment = parts[4];
                        if (parts.length >= 7 && (parts[5] === "p" || parts[5] === "p.")) {// part
                            ret.point = parts[6];
                        }
                    }
                    //ret.url = this.getActUrl(ret.law, ret.paragraph, ret.fragment, ret.point);
                }
                ret.url = this.getActUrl(ret.law, ret.paragraph, ret.fragment, ret.point);
            }
            return ret;
        },
        getLaws: function() {
            var ret = [
                {short: "PS", long: "Eesti Vabariigi põhiseadus", actId: "127042011002"},
                {short: "EIÕK", long: "Inimõiguste ja põhivabaduste kaitse konventsioon", actId: "13320295"},
                {short: "HKMS", long: "Halduskohtumenetluse seadustik", actId: "125102012010"},
                {short: "RVastS", long: "Riigivastutuse seadus", actId: "113092011011"},
                {short: "KOKS", long: "Kohaliku omavalitsuse korralduse seadus", actId: "126032013006"},
                {short: "JäätS", long: "Jäätmeseadus", actId: "114062013006"},
                {short: "LS", long: "Liiklusseadus", actId: "114022014003"}
            ];
            return ret;
        },
        findLawByShort: function(shortName) {
            var laws = this.getLaws();
            for (var lawPos in laws) {
                if (laws[lawPos].short === shortName) {
                    return laws[lawPos];
                }
            }
            return null;
        }
    };
    return LawService;
});
// Angular doesn't have startFrom  
routeExample.filter('startFrom', function() {
    return function(input, start) {
        start = +start; //parse to int
        return input.slice(start);
    };
});
function AngularRouteController($scope, $rootScope, $http/*, $templateCache*/, $timeout) {
    $scope.label = "Hello World!";
    $scope.time = null;
    $scope.status = null;
    $scope.name = null;
    $scope.callTimeRest = false;
    $scope.callRestTime = function() {
        $http({method: 'GET', url: '/rest/time'/*, cache: $templateCache*/}).
                success(function(data, status, headers, config) {
                    $scope.time = data;
                    $scope.view = '/templates/time.html';
                }).
                error(function(data, status, headers, config) {
                    $scope.time = data || "Request failed";
                    $scope.status = status;
                    $scope.view = '/templates/error.html';
                });
    };
    $scope.onTime = function() {
        console.log("On time!");
        if ($scope.callTimeRest) {
            $scope.callRestTime();
        }
        $scope.initOnDemand();
    };
    $scope.init = function() {
        $scope.initOnDemand();
    };
    $rootScope.timerOn = true;
    $scope.initOnDemand = function() {
        if ($rootScope.timerOn) {
            $timeout($scope.onTime, 1000);
        }
    };
    $scope.init();
    $rootScope.headerIsVisible = true;
}

function Page1($scope, $http) {
}

function Page2($scope, $http, $routeParams) {
    $scope.pageID = $routeParams.pageID;
}

function Page3($scope, $http, $routeParams) {
    $scope.pageID = $routeParams.pageID;
}

function Page4($scope, $http, $routeParams, Person) {
    $scope.pageID = $routeParams.pageID;
    $scope.persons = Person.query();
    $scope.search = null;
    $scope.person = Person.get({personId: 5544332211});
    $scope.person.firstName = "Imre";
    $scope.person.lastName = "Tabur";
    $scope.person.$save();
    $scope.person.$delete();
}

function LawPart($scope, $http, $routeParams, LawService) {
    $scope.type = $routeParams.type;
    $scope.short = $routeParams.short;
    $scope.paragraph = $routeParams.paragraph;
    $scope.fragment = $routeParams.fragment;
    $scope.point = $routeParams.point;
    $scope.referenceString = null;
    $scope.reference = null;
    $scope.referenceStringChange = function() {
        if ($scope.referenceString !== undefined || $scope.referenceString !== null) {
            $scope.reference = LawService.stringToReference($scope.referenceString);
        }
    };
}

function UserStory($scope, UserStoryService) {
    $scope.service = UserStoryService;
    $scope.story = UserStoryService.newInstance();
    $scope.roles = UserStoryService.roles;
    $scope.preparedUserStories = UserStoryService.stories;
    $scope.newStory = function() {
        $scope.story = UserStoryService.newInstance();
    };
    $scope.addStory = function() {
        $scope.preparedUserStories = UserStoryService.add($scope.story);
        $scope.newStory();
        $scope.role = null;
    };
    $scope.editStory = function(story) {
        $scope.story = story;
    };
}

function Piusa($scope, $rootScope, PiusaService) {
    $scope.service = PiusaService;
    $rootScope.timerOn = false;
    $rootScope.headerIsVisible = false;
    //$scope.service.shouldDoRounding = true;
    $rootScope.trueFalseIsVisible = false;
    $scope.equalityCheck = function() {
        $scope.numberResult = PiusaService.equalityCheck($scope.numberA, $scope.numberB);
    };
    $scope.equalityCheck();
}

function Book($scope, BookService) {
    $scope.service = BookService;
    $scope.url = null;
    $scope.suffix = null;
    $scope.books = null;
    $scope.booksChapters = null;
    $scope.queryBooks = function() {
        if ($scope.url && $scope.suffix) {
            $scope.service.queryBooks($scope);
        }
    };
}

function Model($scope, $rootScope, $routeParams, ModelService) {
    /*
     $scope.person = Person.get({personId: 5544332211});
     $scope.person.firstName = "Imre";
     $scope.person.lastName = "Tabur";
     $scope.person.$save();
     $scope.person.$delete();
     */
    $scope.service = ModelService;
    $scope.companyID = $routeParams.companyID;
    $scope.service.build($scope);
}
